package com.zone.gateway.core.socket.handler;

import com.zone.gateway.core.mapping.HttpStatement;
import com.zone.gateway.core.session.Configuration;
import com.zone.gateway.core.socket.BaseHandler;
import com.zone.gateway.core.socket.agreement.AgreementConstant;
import com.zone.gateway.core.socket.agreement.GatewayResultMessage;
import com.zone.gateway.core.socket.agreement.ResponseParser;
import com.zone.gateway.core.utils.StringUtils;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.http.DefaultFullHttpResponse;
import io.netty.handler.codec.http.FullHttpRequest;
import io.netty.handler.codec.http.HttpHeaders;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * @author: zongzi
 * @description: 自定义netty鉴权handler
 * @date: 2025/4/23
 */
public class AuthorizationHandler extends BaseHandler<FullHttpRequest> {
    private final Logger logger = LoggerFactory.getLogger(AuthorizationHandler.class);


    private static final String UID = "uId";
    private static final String TOKEN = "token";
    private final Configuration configuration;

    public AuthorizationHandler(Configuration configuration) {
        this.configuration = configuration;
    }

    @Override
    protected void session(ChannelHandlerContext ctx, Channel channel, FullHttpRequest request) {
        HttpStatement httpStatement = channel.attr(AgreementConstant.HTTP_STATEMENT).get();
        // 不需要鉴权，放行请求到下一个handler
        logger.info("authorization handler httpStatement = {}", httpStatement.toString());
        if (!httpStatement.isAuth()) {
            request.retain();
            ctx.fireChannelRead(request);
            return;
        }
        // 从请求头获取信息
        HttpHeaders headers = request.headers();
        String uId = headers.get(UID);
        String token = headers.get(TOKEN);
        if (StringUtils.isEmpty(uId) || StringUtils.isEmpty(token)) {
            // 鉴权不通过
            GatewayResultMessage errorMessage = GatewayResultMessage.newInstant(AgreementConstant.ResponseCode._400, "用户uId和token不能为空");
            DefaultFullHttpResponse response = ResponseParser.createResponse(errorMessage);
            channel.writeAndFlush(response);
            return;
        }
        // 需要鉴权
        boolean isAuth = configuration.auth(uId, token);
        if (isAuth) {
            // 鉴权通过，传递到下一个handler
            request.retain();
            ctx.fireChannelRead(request);
        } else {
            // 鉴权失败
            GatewayResultMessage errorMessage = GatewayResultMessage.newInstant(AgreementConstant.ResponseCode._403, "用户鉴权失败！");
            DefaultFullHttpResponse response = ResponseParser.createResponse(errorMessage);
            channel.writeAndFlush(response);
        }
    }
}
